﻿using System;
using System.Collections.Generic;

namespace Cpuss
{
    /// <summary>
    /// Math utility extension methods.
    /// </summary>
    public static class MathUtil
    {
        /// <summary>
        /// Calculates variance for a given series.
        /// </summary>
        /// <param name="series">Series of values.</param>
        /// <returns>Variance of series.</returns>
        /// <exception cref="ArgumentNullException"><strong>series</strong> is <strong>null</strong>.</exception>
        public static double Variance(this IEnumerable<int> series)
        {
            if (series == null)
            {
                throw new ArgumentNullException("series");
            }

            double mean = series.Mean();
            double total = 0;
            int count = 0;
            foreach (double d in series)
            {
                double temp = d - mean;
                total += (temp)*(temp);
                count++;
            }
            return count == 0 ? 0 : total/count;
        }

        /// <summary>
        /// Calculates variance for a given series.
        /// </summary>
        /// <param name="series">Series of values.</param>
        /// <returns>Variance of series.</returns>
        /// <exception cref="ArgumentNullException"><strong>series</strong> is <strong>null</strong>.</exception>
        public static double Variance(this IEnumerable<double> series)
        {
            if (series == null)
            {
                throw new ArgumentNullException("series");
            }

            double mean = series.Mean();
            double total = 0;
            int count = 0;
            foreach (double d in series)
            {
                double temp = d - mean;
                total += (temp)*(temp);
                count++;
            }
            return count == 0 ? 0 : total/count;
        }

        /// <summary>
        /// Calculates the mean of a series.
        /// </summary>
        /// <param name="series">Series of values.</param>
        /// <returns>Mean of series.</returns>
        /// <exception cref="ArgumentNullException"><strong>series</strong> is <strong>null</strong>.</exception>
        public static double Mean(this IEnumerable<int> series)
        {
            if (series == null)
            {
                throw new ArgumentNullException("series");
            }

            int count = 0;
            double total = 0;
            foreach (double d in series)
            {
                total += d;
                count++;
            }
            return count == 0 ? 0 : total/count;
        }

        /// <summary>
        /// Calculates the mean of a series.
        /// </summary>
        /// <param name="series">Series of values.</param>
        /// <returns>Mean of series.</returns>
        /// <exception cref="ArgumentNullException"><strong>series</strong> is <strong>null</strong>.</exception>
        public static double Mean(this IEnumerable<double> series)
        {
            if (series == null)
            {
                throw new ArgumentNullException("series");
            }

            int count = 0;
            double total = 0;
            foreach (double d in series)
            {
                total += d;
                count++;
            }
            return count == 0 ? 0 : total/count;
        }
    }
}